package geom

import "math"

type Degrees float64
type Radian float64

var AngleTop = Radian(math.Pi / 2)
var AngleTopRight = Radian(math.Pi / 4)
var AngleRight = Radian(0)
var AngleBottomRight = Radian(-math.Pi / 4)
var AngleBottom = Radian(-math.Pi / 2)
var AngleBottomLeft = Radian(-3 * math.Pi / 4)
var AngleLeft = Radian(math.Pi)
var AngleTopLeft = Radian(3 * math.Pi / 4)

func (d Degrees) ToRadians() Radian {
	return Radian(float64(d) * math.Pi / 180)
}

func (d Degrees) ToVec() Vec2 {
	return d.ToRadians().ToVec()
}

func (r Radian) ToVec() Vec2 {
	return Vec2{math.Cos(float64(r)), math.Sin(float64(r))}
}

func (r Radian) ToDegrees() Degrees {
	return Degrees(float64(r) * 180 / math.Pi)
}

func (r Radian) LefterThan(r2 Radian) bool {
	_ = r.ToDegrees()
	_ = r2.ToDegrees()
	if r == r2 {
		return false
	}
	r = r.Normalize()
	r2 = r2.Normalize()
	if math.Abs(float64(r-r2)) < 0.00001 {
		return false
	}
	a := float64((r2 - r).Normalize())
	b := float64(((r + 2*math.Pi) - r2).Normalize())
	return math.Abs(a) > math.Abs(b)
}

func (r Radian) RighterThan(r2 Radian) bool {
	if r == r2 {
		return false
	}

	return r2-r > math.Pi || r2-r < 0
}

func (r Radian) Normalize() Radian {
	for r < 0 {
		r += 2 * math.Pi
	}
	for r >= 2*math.Pi {
		r -= 2 * math.Pi
	}
	return r
}

func (r Radian) NormalizePi2() Radian {
	for r < -math.Pi/2 {
		r += 2 * math.Pi
	}
	for r >= 3*math.Pi/2 {
		r -= 2 * math.Pi
	}
	return r
}

func (r Radian) Near(angle Radian) bool {
	return r.NearEpsilon(angle, 0.01)
}

func (r Radian) NearEpsilon(angle Radian, eps float64) bool {
	return math.Abs(float64(r-angle)) < eps
}

func (d Degrees) Normalize() Degrees {
	for d < 0 {
		d += 360
	}
	for d >= 360 {
		d -= 360
	}
	return d
}
